<!--
 * @Description: 
 * @Version: 2.0
 * @Autor: zhangjx
 * @Date: 2023-05-30 11:43:25
 * @LastEditors: uphldjx 1373577124@qq.com
 * @LastEditTime: 2024-04-24 09:47:32
-->
<template>
	<div>
		<el-input v-model="query" placeholder="请输入菜单名称" @input="onQueryChanged" />
		<!-- default-expand-all -->
		<el-tree
			class="mt10"
			v-bind="$attrs"
			ref="treeRef"
			node-key="id"
			:expand-on-click-node="false"
			highlight-current
			draggable
			:data="treeData"
			:props="defaultProps"
			:filter-method="filterMethod"
			:height="450"
			@node-drop="handleDrop"
			@node-drag-start="dragStart"
		>
			<template #default="{ node, data }">
				<span class="f-between w-100" @mouseenter="onMouseenter(node, data)" @mouseleave="onMouseleave(node, data)">
					<span
						:style="{
							color: data.id === currentId ? '#1f5aff' : '',
							'margin-right': '2rem',
						}"
					>
						{{ node.label }}
					</span>
					<span v-show="data.show">
						<el-button type="primary" text @click.stop="handleEdit(node, data)">
							<icon-edit theme="outline" fill="#333" />
							编辑
						</el-button>
						<el-button type="primary" text>
							<icon-drag theme="outline" fill="#333" />
							移动位置
						</el-button>
					</span>
				</span>
			</template>
		</el-tree>
	</div>
</template>

<script setup lang="ts">
import { ElMessage } from 'element-plus'
import apiMod from '@/apiMod/index'
import type { TreeNode } from 'element-plus/es/components/tree-v2/src/types'
import { useCrudStore } from '@/stores/crud'
const { setMenuTreeData } = useCrudStore()
const query = ref('')
const treeData = ref([])
const treeRef = ref()
const currentId = ref()
const props = defineProps({
	deviceType: [String, Number],
})
const defaultProps = {
	value: 'id',
	label: 'label',
	children: 'children',
}
const emit = defineEmits(['operate'])
const handleEdit = (node, data) => {
	emit('operate', { node, data }, 'edit')
}
const onQueryChanged = (query: string) => {
	treeRef.value!.filter(query)
}
const filterMethod = (query: string, node: TreeNode) => {
	return node.label!.includes(query)
}
const dragStart = (node) => {
	currentId.value = node.data.id
}
const onMouseenter = (node, data) => {
	data.show = true
}
const onMouseleave = (node, data) => {
	data.show = false
}

const updateDrag = (data) => {
	// 更新数据
	apiMod
		.sys_menu_edit({
			...data,
			menuId: data.id,
		})
		.then((res) => {
			ElMessage.success('调整成功')
			getInitData()
		})
}

const handleDrop = (draggingNode, dropNode, dropType) => {
	// 父级id相同移动排序，不同调整上下级
	const dragData = draggingNode?.data
	const dropData = dropNode?.data
	if (dragData.parentId === dropData.parentId) {
		let sort = 999
		if (dropType === 'before') {
			sort = dragData?.sort - 1
		} else {
			sort = dropData.sort + 1
		}
		dragData.sort = sort
		updateDrag(dragData)
	} else {
		updateDrag({
			...dragData,
			menuId: dragData.id,
			parentId: dropType == 'inner' ? dropData.id : dropData.parentId,
		})
	}
}

const appendNode = (data, newChild) => {
	newChild.children = []
	if (!data.children) {
		data.children = []
	}
	data.children.push(newChild)
	treeData.value = [...treeData.value]
}

const removeNode = (node, data) => {
	const parent = data.parent
	const children = parent.data?.children || parent.children
	const index = children.findIndex((d) => d.id === node.id)
	children.splice(index, 1)
	treeData.value = [...treeData.value]
}

const getInitData = () => {
	apiMod.admin_menu({ deviceType: props.deviceType }).then((res) => {
		const data = res.data
		// const keys = res.data.map((item) => item.id)
		// treeRef.value!.setExpandedKeys([...keys, -1])
		treeData.value = data
		setMenuTreeData(data)
	})
}
onMounted(() => {
	getInitData()
})

defineExpose({
	removeNode,
	appendNode,
})
</script>

<style scoped></style>
